<?php

declare(strict_types=1);
/**
 * This file is part of Hyperf.
 *
 * @link     https://www.hyperf.io
 * @document https://hyperf.wiki
 * @contact  group@hyperf.io
 * @license  https://github.com/hyperf/hyperf/blob/master/LICENSE
 */
namespace App\Common\Model;


use think\Collection;
use think\db\exception\DataNotFoundException;
use think\db\exception\DbException;
use think\db\exception\ModelNotFoundException;
use think\facade\Db;
use think\Model as BaseModel;
use think\model\concern\SoftDelete;

abstract class Model extends BaseModel
{
    use SoftDelete;

    /**
     * The storage format of the model's date columns.
     *
     * @var string|null
     */
    protected $dateFormat = 'Y-m-d H:i:s';

    protected $updateTime = 'update_time';
    protected $createTime = 'create_time';

    protected string $deleteTime = 'delete_time';

    /**
     * 属性转换的默认值
     */
    final protected const DEFAULT_CASTS = [
        'deleted_time' => 'int',
        'updated_time' => 'datetime',
        'created_time' => 'datetime',
    ];

    /**
     * The attributes that should be cast.
     *
     * @var array
     */
    protected $type = self::DEFAULT_CASTS;

    protected $hidden = ['delete_time'];

    protected $jsonAssoc = true;

    /**
     * @return string
     */
    public function getPrimaryKey(): string
    {
        return $this->getPk();
    }

    /**
     * 获取所有表
     *
     * @return Collection
     */
    public static function getAllTable(): Collection
    {
        $data = Db::query('SELECT TABLE_COMMENT,TABLE_NAME FROM information_schema.TABLES WHERE table_schema=:s', [
            's' => self::getSchema()
        ]);

        return collect($data);
    }

    /**
     * @param string $label
     * @param string $value
     * @return array
     * @throws DataNotFoundException
     * @throws DbException
     * @throws ModelNotFoundException
     */
    public static function getSelectData(string $label, string $value = 'id'): array
    {
        return self::field(["$label as label", "$value as value"])->select()->toArray();
    }

    /**
     * 获取表前缀
     *
     * @return mixed|string
     */
    public static function getPrefix(): mixed
    {
        return config('database.connections.mysql.prefix') ?: 'sc_';
    }

    /**
     * 获取数据库
     *
     * @return string
     */
    public static function getSchema(): string
    {
        return config('database.connections.mysql.database') ?: '';
    }

    /**
     * @return string
     */
    public function getUpdateTimeField(): string
    {
        return $this->updateTime;
    }

    /**
     * @return string
     */
    public function getCreateTimeField(): string
    {
        return $this->createTime;
    }


    public function isDirty(array $fields = null): bool
    {
        if ($fields === null) {
            return $this->getChangedData() !== [];
        }
        return array_intersect_key($this->getChangedData(), array_flip($fields)) !== [];
    }
}
